//
//  MyDefaultCacheBehavior.swift
//
//
//  Created by lvzhao on 2024/5/25.
//

import Foundation

// MyDefaultCacheBehavior 可以存储任意类型的数据, 但是若选择了加密的方式, 目前只支持String & data的方式, 其他类型暂时不支持, 需要自己去拓展

open class MyDefaultCacheBehavior: MyCacheBehavior {
    
    public func get<T>(key: String, isDecrypt: Bool) -> T? {
        if isDecrypt {
            //读取解密后的数据
            return getDecryptData(key: key)
        } else {
            //读取原数据
            return getOriginalDada(key: key)
        }
    }
    
    public func set<T>(key: String, data: T, isEncrypt: Bool) -> MyStoreErrorCode {
        if isEncrypt {
            return setEncryptData(key: key, data: data)
        } else {
            return setOriginalData(key: key, data: data)
        }
    }
}


public extension MyDefaultCacheBehavior {
        
    //获取原数据
    func getOriginalDada<T>(key: String) -> T? {
        guard let item = UserDefaults.standard.object(forKey: key) as? T else { return nil }
        return item
    }
    
    
    func setOriginalData<T>(key: String, data: T) -> MyStoreErrorCode {
        UserDefaults.standard.setValue(data, forKey: key)
        return .success
    }
    
    
    func getDecryptData<T>(key:String) -> T? {
        if let item = UserDefaults.standard.object(forKey: key) as? String {
            guard let deString = MyCryptManager().decrypt(key: key, strToDecode: item, type: .aes) else { return nil}
            guard let deItem = deString as? T else { return nil }
            return deItem
        } else if let dataItem = UserDefaults.standard.object(forKey: key) as? Data {
            let newStr = String(data: dataItem,encoding: String.Encoding.utf8)
            guard let deString = MyCryptManager().encrypt(key: key, strToEncode: newStr, type: .aes) else {return nil}
            let deData = deString.data(using: String.Encoding.utf8)
            guard let deItem = deData as? T else {
                return nil
            }
            return deItem
            
        } else {
            return nil
        }
    }
    
    func setEncryptData<T>(key: String, data: T) -> MyStoreErrorCode {
        if let strItem = data as? String {
            guard let enString = MyCryptManager().encrypt(key: key, strToEncode: strItem, type: .aes) else {
                return .setError
            }
            UserDefaults.standard.set(enString, forKey: key)
            return .success
        } else if let dataItem = data as? Data {
            let newStr = String(data: dataItem, encoding: String.Encoding.utf8)
            guard let enSting = MyCryptManager().encrypt(key: key, strToEncode: newStr, type: .aes) else {return .setError}
            let enData = enSting.data(using: String.Encoding.utf8)
            UserDefaults.standard.set(enData, forKey: key)
            return .success
        } else {
            return .setError
        }
    }
}





